package com.gxc.authcore.client.filter;

import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import com.gxc.authcore.client.cache.AuthCacheClient;
import com.gxc.authcore.client.controller.AuthClientController;
import com.gxc.authcore.system.util.AuthInfo;
import com.gxc.authcore.system.util.CheckUtil;
import com.gxc.authcore.system.util.CurrentUtil;
import com.gxc.authcore.system.util.ParamUtil;
import com.gxc.authcore.system.util.SerializeUtil;
import com.gxc.authcore.system.util.ViewUtil;
import com.gxc.webcore.util.ContextUtil;
import com.gxc.webcore.util.JsonUtil;
import com.gxc.webcore.util.SystemUtil;

/**
 * 认证过滤器
 * 
 * @author gxc
 * 
 */
public class AuthFilter implements Filter {

	public void init(FilterConfig filterConfig) throws ServletException {
	}

	public void doFilter(ServletRequest request, ServletResponse response,
			FilterChain chain) throws IOException, ServletException {

		// TODO 设置线程的当前request,response,authid,authCache
		HttpServletRequest hrequest = (HttpServletRequest) request;
		HttpServletResponse hresponse = (HttpServletResponse) response;
		CurrentUtil.setRequest(hrequest);
		CurrentUtil.setResponse(hresponse);
		HttpSession session = hrequest.getSession();
		String authid = (String) session.getAttribute("authid");
		AuthInfo authInfo = AuthCacheClient.getAuthInfo(authid);
		if (authInfo != null) {
			CurrentUtil.setAuthid(authid);
			CurrentUtil.setAuthInfo(authInfo);
		} else {
			CurrentUtil.setAuthid(null);
			CurrentUtil.setAuthInfo(null);
		}
		// TODO 请求url
		String url = hrequest.getPathInfo() == null ? hrequest.getServletPath()
				: hrequest.getPathInfo();
		url = url.trim();
		while (url.startsWith("/")) {
			url = url.substring(1);
		}
		// TODO 登录校验
		if (CheckUtil.needCheck(url) && !CheckUtil.checkLogin(url)) {
			this.redirectView();
			return;
		}
		// TODO 权限校验
		boolean flag_access = CheckUtil.checkAccess(url);
		if (!flag_access) {
			ViewUtil.redirectToNoAccessView();
			return;
		}
		// chain.dofilter
		chain.doFilter(request, response);
	}

	public void destroy() {
	}

	/**
	 * 跳转
	 * 
	 * @return
	 * @throws Exception
	 */
	@SuppressWarnings({ "unchecked", "rawtypes" })
	protected void redirectView() {
		HttpServletRequest request = CurrentUtil.getRequest();
		String requestMethod = request.getHeader("X-Requested-With");
		String jsonpCallback = request.getHeader("jsonpCallback");
		String loginUrl = null;
		if (SystemUtil.get("systemMode").equals("single")) {
			// 单机模式
			loginUrl = ParamUtil.get("url_local") + "/common/auth/login.do";
		} else {
			// 集成模式
			loginUrl = ParamUtil.get("url_authcenter")
					+ "/common/auth/login.do";
		}
		if (requestMethod != null && requestMethod.equals("XMLHttpRequest")) {
			// normal ajax request
			Map result = new HashMap();
			result.put("status", "failed");
			result.put("data", "您尚未登陆，或登陆已超时，<a href='" + loginUrl
					+ "'>请先登陆</a>。");
			String json_result = JsonUtil.object2json(result);
			try {
				CurrentUtil.getResponse().getWriter().write(json_result);
			} catch (IOException e) {
				e.printStackTrace();
			}
			return;
		} else if (jsonpCallback != null && !jsonpCallback.isEmpty()) {
			// jsonp request
			Map result = new HashMap();
			result.put("status", "failed");
			result.put("data", "您尚未登陆，或登陆已超时，<a href='" + loginUrl
					+ "'>请先登陆</a>。");
			String json_result = JsonUtil.object2jsonp(result, jsonpCallback);
			try {
				CurrentUtil.getResponse().getWriter().write(json_result);
			} catch (IOException e) {
				e.printStackTrace();
			}
			return;
		} else {
			// normal webpage request
			if (SystemUtil.get("systemMode").equals("single")) {
				// 单机模式
				try {
					String url = ParamUtil.get("url_local")
							+ "/common/auth/login.do"
							+ SerializeUtil.serializeRedirectParam(CurrentUtil
									.getRequest());
					CurrentUtil.getResponse().sendRedirect(url);
				} catch (IOException e) {
					e.printStackTrace();
				}
			} else {
				// 集成模式
				AuthClientController controller = (AuthClientController) ContextUtil
						.getBean(AuthClientController.class);
				try {
					controller.redirectToAuth(CurrentUtil.getRequest(),
							CurrentUtil.getResponse());
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
			return;
		}
	}

}
